

#ifndef P_POLYNOMIAL_INCLUDED
#define P_POLYNOMIAL_INCLUDED
#include <vector>
#include "Polynomial.h"

template<int Degree>
class StartingPolynomial{
public:
	Polynomial<Degree> p;
	//变量定义域
	double start;

	template<int Degree2>
	StartingPolynomial<Degree+Degree2>  operator * (const StartingPolynomial<Degree2>& p) const;
	StartingPolynomial scale(double s) const;
	StartingPolynomial shift(double t) const;
	int operator < (const StartingPolynomial& sp) const;
	static int Compare(const void* v1,const void* v2);
};

template<int Degree>
class PPolynomial
{
public:
	size_t polyCount;
	StartingPolynomial<Degree>* polys;

	PPolynomial(void);
	PPolynomial(const PPolynomial<Degree>& p);
	~PPolynomial(void);

	PPolynomial& operator = (const PPolynomial& p);

	int size(void) const;

	void set( size_t size );
	// Note: this method will sort the elements in sps
	void set( StartingPolynomial<Degree>* sps , int count );
	void reset( size_t newSize );


	double operator()( double t ) const;
	double integral( double tMin , double tMax ) const;
	double Integral( void ) const;

	template<int Degree2>
	PPolynomial<Degree>& operator = (const PPolynomial<Degree2>& p);

	PPolynomial  operator + (const PPolynomial& p) const;
	PPolynomial  operator - (const PPolynomial& p) const;

	template<int Degree2>
	PPolynomial<Degree+Degree2> operator * (const Polynomial<Degree2>& p) const;

	template<int Degree2>
	PPolynomial<Degree+Degree2> operator * (const PPolynomial<Degree2>& p) const;


	PPolynomial& operator += ( double s );
	PPolynomial& operator -= ( double s );
	PPolynomial& operator *= ( double s );
	PPolynomial& operator /= ( double s );
	PPolynomial  operator +  ( double s ) const;
	PPolynomial  operator -  ( double s ) const;
	PPolynomial  operator *  ( double s ) const;
	PPolynomial  operator /  ( double s ) const;

	PPolynomial& addScaled(const PPolynomial& poly,double scale);

	PPolynomial scale( double s ) const;
	PPolynomial shift( double t ) const;

	PPolynomial< Degree-1 > derivative(void) const;
	PPolynomial< Degree+1 > integral(void) const;

	void getSolutions(double c,std::vector<double>& roots,double EPS,double min=-DBL_MAX,double max=DBL_MAX) const;

	void printnl( void ) const;

	PPolynomial< Degree+1 > MovingAverage( double radius ) const;
	static PPolynomial BSpline( double radius=0.5 );

	void write( FILE* fp , int samples , double min , double max ) const;
};
#include "PPolynomial.inl"
#endif // P_POLYNOMIAL_INCLUDED
